#include<stdio.h>
#include<pcap/pcap.h>
#include<sys/types.h>
#include<string.h>
#include "jp_mysql_h.h"
#include "jp_net_h.h"
/*********
arg: net format u_short
**********/
char* recog_eth_protocol(u_short argtype){
	u_short _type=ntohs(argtype);
	switch(_type){
		case IPv4:
		return "IPv4";
		break;
		case ARP:
		return "ARP";
		break;
		case PPPoE:
		return "PPPoE";
		break;
		case TAGQ:
		return "802.1Q tag";
		break;
		case IPv6:
		return "IPv6";
		break;
		case MPLS:
		return "MPLS Label";
		break;
	}
	return "unrecognition";
}
/******************************************
返回协议字符串，
arg:协议号
******************************************/
char *recog_ip_protocol(u_char prol){
	switch(prol){
		case ICMP:
		return "ICMP";
		break;
		case IGMP:
		return "IGMP";
		break;
		case GGP:
		return "GGP";
		break;
		case IPENCAP:
		return "IP-ENCAP";
		break;
		case ST:
		return "ST";
		break;
		case TCP:
		return "TCP";
		break;
		case EGP:
		return "EGP";
		break;
		case PUP:
		return "PUP";
		break;
		case UDP:
		return "UDP";
		break;
		case HMP:
		return "HMP";
		break;
	
	}
	return "UNRECOG";
}
/*******
to mac address ,arg:net format
*******/
void to_mac(const u_char *netaddr,char *buf){
	//buf=(char )malloc(17);
	memset(buf,0,17);
	//printf("aaaaaaaaaaaaa\n");
	sprintf(buf,"%02x:%02x:%02x:%02x:%02x:%02x",netaddr[0],netaddr[1],netaddr[2],netaddr[3],netaddr[4],netaddr[5]);
	//printf("%sxxxxxxxxxxxxxxxxxx\n",buf);
	//printf("sssssssssss\n");
	//return NULL;
}
/**********************************************
记录MAC地址
**********************************************/
void record_mac(const struct eth_header *eth){
	 char buf[17],buf2[17];
	 to_mac(eth->eth_dhost,buf);
         to_mac(eth->eth_shost,buf2);
         jp_add_mac(buf2);
	 jp_add_mac(buf);
         jp_update_protocol(buf2,recog_eth_protocol(eth->eth_type));
	 jp_update_protocol(buf,recog_eth_protocol(eth->eth_type));

}
/*****************************************************
记录ip地址
*****************************************************/
void record_ip(const struct eth_header *eth,const struct jp_ip_header *ip){
	char smac[17],dmac[17];
	to_mac(eth->eth_shost,smac);
	to_mac(eth->eth_dhost,dmac);
	char sip[16],dip[16];
        strcpy(sip,inet_ntoa(ip->ip_src));
	strcpy(dip,inet_ntoa(ip->ip_dst));

	jp_update_ip(smac,sip);
	jp_update_ip(dmac,dip);
	printf("mac(%s),ip:%s\n",dmac,dip);
}
void do_cap(u_char *arg,const struct pcap_pkthdr *pkthdr,const u_char *packet){
	//printf("execute do cap\n");
	const struct eth_header *eth;
	const struct jp_ip_header *ip;
	/*
	char buf[17],buf2[17];
	char prol[255];
	eth=(struct eth_header *)packet;
	to_mac(eth->eth_dhost,buf);
	to_mac(eth->eth_shost,buf2);
	jp_add_mac(buf2);
	jp_update_protocol(buf2,recog_eth_protocol(eth->eth_type));
	*/
	eth=(struct eth_header *)packet;
	record_mac(eth);
	//to_mac(eth->eth_shost,smac);
	u_short _p=ntohs(eth->eth_type);
	if(_p==IPv4){
		ip=(struct jp_ip_header *)(packet+JP_ETH_LEN);
		record_ip(eth,ip);      
	}
	//printf("%s====%s====>%s\n",buf2,recog_eth_protocol(eth->eth_type),buf);
	//printf("protocol:%s\n",recog_eth_protocol(eth->eth_type));
}

int main(){
	char *devname,errorbuf[PCAP_ERRBUF_SIZE];
	//const struct eth_header *eth;
	pcap_t *hcap;
	struct pcap_pkthdr header;
	const u_char *packet;
	devname=pcap_lookupdev(errorbuf);
	if(devname==NULL){
		printf("is error,error message:%s",errorbuf);
	}else
	{
	//	printf("success,dev name:%s",devname);
		hcap=pcap_open_live(devname,2048,1,0,errorbuf);
	//	packet=pcap_next();
		if(hcap==NULL){
			printf("\nerror:%s",errorbuf);
		}else{
			//printf("live success!");
			//int i=0;
			//while(1){
				/***********
				packet=pcap_next(hcap,&header);
				eth=(struct eth_header *)packet;
				printf("prop:%s\r",recog_eth_protocol(eth->eth_type));
				//sleep(2000);
				************/
				pcap_loop(hcap,-1,do_cap,NULL);
				//i++;
				printf("\n\nexecuste\n\n");
				//printf("\ni:%d\n",i);
			//}
			pcap_close(hcap);
		}
	}
	printf("\n");
	return 0;
}
